package com.klm.easymq.controller;

import com.klm.easymq.core.MonitorService;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.format.annotation.DateTimeFormat;
import org.springframework.web.bind.annotation.*;

import java.time.LocalDateTime;
import java.time.format.DateTimeFormatter;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

/**
 * Easy-MQ 故障排查控制器
 * 提供专门的故障诊断和排查功能
 */
@Slf4j
@RestController
@RequestMapping("/easymq/api/fault-diagnosis")
public class EasyMqFaultDiagnosisController {
    
    @Autowired
    private MonitorService monitorService;
    
    private final DateTimeFormatter formatter = DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss");
    
    /**
     * 查询失败的消息记录
     */
    @GetMapping("/failed-messages")
    public Map<String, Object> getFailedMessages(
            @RequestParam(required = false) String topic,
            @RequestParam(required = false) @DateTimeFormat(pattern = "yyyy-MM-dd HH:mm:ss") LocalDateTime startTime,
            @RequestParam(required = false) @DateTimeFormat(pattern = "yyyy-MM-dd HH:mm:ss") LocalDateTime endTime,
            @RequestParam(defaultValue = "100") int limit) {
        
        Map<String, Object> result = new HashMap<>();
        
        try {
            String startTimeStr = startTime != null ? startTime.format(formatter) : null;
            String endTimeStr = endTime != null ? endTime.format(formatter) : null;
            
            List<Map<String, Object>> failedMessages = monitorService.queryFailedMessages(topic, startTimeStr, endTimeStr, limit);
            
            result.put("success", true);
            result.put("data", failedMessages);
            result.put("count", failedMessages.size());
            result.put("queryTime", LocalDateTime.now().format(formatter));
            
        } catch (Exception e) {
            log.error("Failed to query failed messages", e);
            result.put("success", false);
            result.put("error", e.getMessage());
        }
        
        return result;
    }
    
    /**
     * 查询消费者生命周期事件
     */
    @GetMapping("/consumer-lifecycle")
    public Map<String, Object> getConsumerLifecycle(
            @RequestParam(required = false) String consumerId,
            @RequestParam(required = false) String group,
            @RequestParam(required = false) @DateTimeFormat(pattern = "yyyy-MM-dd HH:mm:ss") LocalDateTime startTime,
            @RequestParam(required = false) @DateTimeFormat(pattern = "yyyy-MM-dd HH:mm:ss") LocalDateTime endTime) {
        
        Map<String, Object> result = new HashMap<>();
        
        try {
            String startTimeStr = startTime != null ? startTime.format(formatter) : null;
            String endTimeStr = endTime != null ? endTime.format(formatter) : null;
            
            List<Map<String, Object>> lifecycleEvents = monitorService.queryConsumerLifecycle(consumerId, group, startTimeStr, endTimeStr);
            
            result.put("success", true);
            result.put("data", lifecycleEvents);
            result.put("count", lifecycleEvents.size());
            result.put("queryTime", LocalDateTime.now().format(formatter));
            
        } catch (Exception e) {
            log.error("Failed to query consumer lifecycle", e);
            result.put("success", false);
            result.put("error", e.getMessage());
        }
        
        return result;
    }
    
    /**
     * 查询连接状态变化历史
     */
    @GetMapping("/connection-history")
    public Map<String, Object> getConnectionHistory(
            @RequestParam(required = false) String adapterType,
            @RequestParam(required = false) @DateTimeFormat(pattern = "yyyy-MM-dd HH:mm:ss") LocalDateTime startTime,
            @RequestParam(required = false) @DateTimeFormat(pattern = "yyyy-MM-dd HH:mm:ss") LocalDateTime endTime) {
        
        Map<String, Object> result = new HashMap<>();
        
        try {
            String startTimeStr = startTime != null ? startTime.format(formatter) : null;
            String endTimeStr = endTime != null ? endTime.format(formatter) : null;
            
            List<Map<String, Object>> connectionHistory = monitorService.queryConnectionHistory(adapterType, startTimeStr, endTimeStr);
            
            result.put("success", true);
            result.put("data", connectionHistory);
            result.put("count", connectionHistory.size());
            result.put("queryTime", LocalDateTime.now().format(formatter));
            
        } catch (Exception e) {
            log.error("Failed to query connection history", e);
            result.put("success", false);
            result.put("error", e.getMessage());
        }
        
        return result;
    }
    
    /**
     * 获取故障统计信息
     */
    @GetMapping("/failure-stats")
    public Map<String, Object> getFailureStats(
            @RequestParam(required = false) @DateTimeFormat(pattern = "yyyy-MM-dd HH:mm:ss") LocalDateTime startTime,
            @RequestParam(required = false) @DateTimeFormat(pattern = "yyyy-MM-dd HH:mm:ss") LocalDateTime endTime) {
        
        Map<String, Object> result = new HashMap<>();
        
        try {
            String startTimeStr = startTime != null ? startTime.format(formatter) : null;
            String endTimeStr = endTime != null ? endTime.format(formatter) : null;
            
            Map<String, Object> failureStats = monitorService.getFailureStats(startTimeStr, endTimeStr);
            
            result.put("success", true);
            result.put("data", failureStats);
            result.put("queryTime", LocalDateTime.now().format(formatter));
            
        } catch (Exception e) {
            log.error("Failed to get failure stats", e);
            result.put("success", false);
            result.put("error", e.getMessage());
        }
        
        return result;
    }
    
    /**
     * 根据traceId查询完整消息链路
     */
    @GetMapping("/message-trace/{traceId}")
    public Map<String, Object> getMessageTrace(@PathVariable String traceId) {
        Map<String, Object> result = new HashMap<>();
        
        try {
            List<Map<String, Object>> messageRecords = monitorService.queryByTraceId(traceId);
            
            result.put("success", true);
            result.put("traceId", traceId);
            result.put("data", messageRecords);
            result.put("count", messageRecords.size());
            result.put("queryTime", LocalDateTime.now().format(formatter));
            
        } catch (Exception e) {
            log.error("Failed to query message trace: {}", traceId, e);
            result.put("success", false);
            result.put("error", e.getMessage());
        }
        
        return result;
    }
    
    /**
     * 获取故障诊断概览
     */
    @GetMapping("/overview")
    public Map<String, Object> getDiagnosisOverview(
            @RequestParam(defaultValue = "24") int hours) {
        
        Map<String, Object> result = new HashMap<>();
        
        try {
            LocalDateTime endTime = LocalDateTime.now();
            LocalDateTime startTime = endTime.minusHours(hours);
            
            String startTimeStr = startTime.format(formatter);
            String endTimeStr = endTime.format(formatter);
            
            // 获取故障统计
            Map<String, Object> failureStats = monitorService.getFailureStats(startTimeStr, endTimeStr);
            
            // 获取连接状态变化
            List<Map<String, Object>> connectionHistory = monitorService.queryConnectionHistory(null, startTimeStr, endTimeStr);
            
            // 获取消费者生命周期事件
            List<Map<String, Object>> lifecycleEvents = monitorService.queryConsumerLifecycle(null, null, startTimeStr, endTimeStr);
            
            // 获取失败消息
            List<Map<String, Object>> failedMessages = monitorService.queryFailedMessages(null, startTimeStr, endTimeStr, 10);
            
            Map<String, Object> overview = new HashMap<>();
            overview.put("failureStats", failureStats);
            overview.put("connectionEvents", connectionHistory.size());
            overview.put("consumerEvents", lifecycleEvents.size());
            overview.put("recentFailures", failedMessages);
            overview.put("timeRange", Map.of(
                "startTime", startTimeStr,
                "endTime", endTimeStr,
                "hours", hours
            ));
            
            result.put("success", true);
            result.put("data", overview);
            result.put("queryTime", LocalDateTime.now().format(formatter));
            
        } catch (Exception e) {
            log.error("Failed to get diagnosis overview", e);
            result.put("success", false);
            result.put("error", e.getMessage());
        }
        
        return result;
    }
    
    /**
     * 导出故障诊断报告
     */
    @GetMapping("/export")
    public Map<String, Object> exportDiagnosisReport(
            @RequestParam(required = false) @DateTimeFormat(pattern = "yyyy-MM-dd HH:mm:ss") LocalDateTime startTime,
            @RequestParam(required = false) @DateTimeFormat(pattern = "yyyy-MM-dd HH:mm:ss") LocalDateTime endTime,
            @RequestParam(defaultValue = "1000") int limit) {
        
        Map<String, Object> result = new HashMap<>();
        
        try {
            String startTimeStr = startTime != null ? startTime.format(formatter) : null;
            String endTimeStr = endTime != null ? endTime.format(formatter) : null;
            
            // 收集所有相关数据
            Map<String, Object> report = new HashMap<>();
            
            // 故障统计
            report.put("failureStats", monitorService.getFailureStats(startTimeStr, endTimeStr));
            
            // 失败消息
            report.put("failedMessages", monitorService.queryFailedMessages(null, startTimeStr, endTimeStr, limit));
            
            // 连接历史
            report.put("connectionHistory", monitorService.queryConnectionHistory(null, startTimeStr, endTimeStr));
            
            // 消费者生命周期
            report.put("consumerLifecycle", monitorService.queryConsumerLifecycle(null, null, startTimeStr, endTimeStr));
            
            // 报告元数据
            report.put("metadata", Map.of(
                "startTime", startTimeStr,
                "endTime", endTimeStr,
                "exportTime", LocalDateTime.now().format(formatter),
                "limit", limit
            ));
            
            result.put("success", true);
            result.put("data", report);
            result.put("exportTime", LocalDateTime.now().format(formatter));
            
        } catch (Exception e) {
            log.error("Failed to export diagnosis report", e);
            result.put("success", false);
            result.put("error", e.getMessage());
        }
        
        return result;
    }
} 